package cn.hetra.hj212;

import cn.hetra.hj212.core.CPS;
import cn.hetra.hj212.core.HJ212Data;
import cn.hetra.hj212.session.SessionImpl;
import cn.hetra.hj212.service.HJ212DataHandler;
import cn.hetra.hj212.service.RemotingService;
import cn.hetra.hj212.service.dto.CN2011UploadedData;
import cn.hetra.hj212.service.dto.CN2031UploadedData;
import cn.hetra.hj212.service.dto.CN2051UploadedData;
import cn.hetra.hj212.service.dto.CN2061UploadedData;
import io.netty.channel.Channel;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.SimpleChannelInboundHandler;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.ObjectProvider;
/**
 *
 */
public class NettyTcpInboundHandler extends SimpleChannelInboundHandler<HJ212Data> {

    private static final Logger LOGGER = LoggerFactory.getLogger(NettyTcpInboundHandler.class);

    private RemotingService remotingService;

    ObjectProvider<HJ212DataHandler> hj212DataHandler;



    public NettyTcpInboundHandler(RemotingService remotingService,ObjectProvider<HJ212DataHandler> hj212DataHandler){
        this.remotingService = remotingService;
        this.hj212DataHandler = hj212DataHandler;
    }



    @Override
    public void channelActive(ChannelHandlerContext ctx) throws Exception {
        remotingService.addConnectionEntry(ctx.channel());
        ctx.fireChannelActive();
    }
    @Override
    public void channelInactive(ChannelHandlerContext ctx) throws Exception {
        remotingService.removeConnection(ctx.channel().id());
        ctx.fireChannelInactive();
    }

    @Override
    protected void channelRead0(ChannelHandlerContext ctx, HJ212Data msg) throws Exception {
        Channel channel = ctx.channel();
        String CN = msg.getCN();
        ctx.channel().attr(HJ212Data.ST_ATTR).set(msg.getST());
        ctx.channel().attr(HJ212Data.PW_ATTR).set(msg.getPW());
        ctx.channel().attr(HJ212Data.VERSION_ATTR).set(msg.getVersion());
        ctx.channel().attr(HJ212Data.MN_ATTR).set(msg.getMN());
        SessionImpl session = remotingService.registerMN(ctx.channel());//设备唯一编码
        if("9011".equals(CN)){
            //请求应答结果
            //上传的报文有分包的话，每个具体的分包的CN也会不一样
            session.handleComplete(msg);
        } else if("2011".equals(CN)){
            //上传污染物实时数据
            //现场机以上传污染物实时数据间隔为周期发送“污染物实时数据”；
            //上位机接收“上传污染物实时数据”命令并执行，根据标志 Flag 的值决定是否返回“数据应答”；
            //"-Rtd"
            //-Flag
            //-SampleTime
            //-EFlag
            CPS.CPSGroups parse = msg.getCps().new Parser().parseGroup("-Rtd", "-Flag", "-SampleTime", "-EFlag");
            String dataTime = parse.getInfos().get("DataTime");
            hj212DataHandler.ifAvailable(handler->{
                handler.handleRealData(new CN2011UploadedData(dataTime,msg.getMN(),parse.getGroups()));
            });
        }else if("2051".equals(CN)){
            System.out.println(msg);
            //上传污染物分钟数据
            CPS.CPSGroups parse = msg.getCps().new Parser().parseGroup("-Cou", "-Min", "-Avg", "-Max","-Flag");
            /*
               数据时间，表示一个时间段的开始时间点，时间精确到分钟；若分钟数据上
                报时间间隔取值为 10 分钟，则 20160801084000 表示上报数据为时间段 2016
                年 8 月 1 日 8 时 40 分 0 秒到 2016 年 8 月 1 日 8 时 50 分 0 秒之间的污染物分
                钟数据
             */
            String dataTime = parse.getInfos().get("DataTime");
            hj212DataHandler.ifAvailable(handler->{
                handler.handleMinuteData(new CN2051UploadedData(dataTime,msg.getMN(),parse.getGroups()));
            });
        }else if("2061".equals(CN)){
            //HJ212 小时数据，无设置时间间隔，固定1小时
            //上传污染物小时数据
            CPS.CPSGroups parse = msg.getCps().new Parser().parseGroup("-Cou", "-Min", "-Avg", "-Max","-Flag");
            String dataTime = parse.getInfos().get("DataTime");//时间精确到小时； 20160801080000
            hj212DataHandler.ifAvailable(handler->{
                handler.handleHourData(new CN2061UploadedData(dataTime,msg.getMN(),parse.getGroups()));
            });
        }else if("2031".equals(CN)){
            //HJ212 日数据，无设置时间间隔，固定一天
            //上传污染物日历史数据
            CPS.CPSGroups parse = msg.getCps().new Parser().parseGroup("-Cou", "-Min", "-Avg", "-Max","-Flag");
            String dataTime = parse.getInfos().get("DataTime");//数据时间，表示一个时间段的开始时间点，时间精确到日
            hj212DataHandler.ifAvailable(handler->{
                handler.handleDayData(new CN2031UploadedData(dataTime,msg.getMN(),parse.getGroups()));
            });
        }else if("2041".equals(CN)){

        }else if("3020".equals(CN)){

        }else if("2081".equals(CN)){
            /*
            1、数采仪开机联网后发送“上传数采仪开机时间”命令；
2、上位机接收“上传数采仪开机时间”命令并执行，根据标志 Flag 的值决定是否返回“数据应答”；
3、如果“上传数采仪开机时间”命令需要数据应答，现场机接收“数据应答”，请求执行完毕
             */
        }else if("3019".equals(CN)){
            //1、在线监控（监测）仪器仪表发生更换时发送“上传设备唯一标识”命令
        }
        if(1==msg.getD()){
            //需要应答
            HJ212Data.Builder res = new HJ212Data.Builder(msg);
            res.ST("91");
            res.CN("9014");
            //不需要应答
            res.clearCP();
            channel.writeAndFlush(res.build());
        }
    }
}
